---
title: "[deprecated] Integration configuration (nango.yaml)"
sidebarTitle: "[deprecated] Integration config (nango.yaml)"
icon: "arrow-right-arrow-left"
---

Integrations are configured in the `nango.yaml` file, which lives in your code base.

# Example

```yaml nango.yaml
integrations:
  asana: # Integration ID.
    syncs:
      asana-fetch-tasks: # Sync name.
        description: | # Sync description.
          Some long description, some long description, some long description,
          some long description, some long description, some long description.
        output: AsanaTask # Synced model
        endpoint: # Generated endpoint to access the synced model.
          method: GET
          path: /tasks
          group: Tasks
        sync_type: incremental # Data is replaced ('full') or upserted ('incremental') on each sync execution.
        runs: every 30min # Sync frequency.
        input:  AsanaProject # Necessary input to execute the sync.
        scopes: # Required scopes.
          - scope1
          - scope2
        auto_start: true # If true, data syncing starts when a new connection is created.
        track_deletes: true # If true, automatically detects deleted records (for full refresh syncs only).
        webhook-subscriptions: # The types of webhook this sync handles.
          - event_type_1
          - event_type_2

    actions:
      asana-create-task:
        description: | # Action description.
          Some long description, some long description, some long description,
          some long description, some long description, some long description.
        output: AsanaTask # Returned model
        endpoint: # Generated endpoint to trigger to action.
          method: POST
          path: /tasks
          group: Tasks
        input: # Necessary input to execute the action.
        scopes: # Required scopes.
          - scope1
          - scope2

    on-events:
        validate-connection:
            - verify-credentials
        post-connection-creation:
            - setup
            - moreSetup
        pre-connection-deletion:
            - cleanup

models:
  AsanaTask: # Schema for sync output AND action input/output.
    id: string # Required unique field for sync output models.
    project_id: string
    name: string
    completed: boolean
    created_at: date
    modified_at: date

  AsanaProject: # Schema for sync input.
    id: string
```

# Integrations fields

Integration configuration fields are under `integrations.<INTEGRATION-ID>`.

<ResponseField name="syncs" type="object">
  Lists the syncs for a given integration.
</ResponseField>

<ResponseField name="actions" type="object">
  Lists the actions for a given integration.
</ResponseField>

<ResponseField name="on-events" type="object">
  Lists the events and functions executed when those events occur.
</ResponseField>

### Sync fields

Sync configuration fields are under `integrations.<INTEGRATION-ID>.syncs.<SYNC-NAME>`.

<ResponseField name="description" type="string" required>
  Describes the sync.
</ResponseField>

<ResponseField name="output" type="string" required>
  Defines the schema of the data you want to sync. References a schema from the [Models](#model-fields) section of this configuration file.

  Each sync has a corresponding generated endpoint to fetch the data, configured in the `endpoint` field below.

  <Tip>
    Syncs can have multiple output models. This is useful when there is some form of dependency between the two models, e.g.

    - Fetching the data for a model from the external API requires fetching the data from another model first
    - You want the records of one model to be persisted before the records of another model

    When defining multiple output models, you must define as many endpoints. The 1st endpoint will return the 1st model, the 2nd endpoint the 2nd model, etc.

    Here's an example:

    ```yaml
      asana-fetch-tasks-and-comments:
        output:
          - AsanaTask
          - AsanaComment
        endpoint:
          - method: GET
            path: /tasks
          - method: GET
            path: /comments
    ```
  </Tip>
</ResponseField>

<ResponseField name="endpoint" type="string|object" required>
  Defines the endpoint to use to fetch the output model.

  ```yaml
  endpoint:
    method: GET
    path: /tasks
    group?: Tasks
  ```

  Possible method values are: `GET`

  The method/endpoint combination can be shared across syncs to unify the communication with external APIs.
  The `group` is an optional value to group endpoints across functions.

  Legacy format: `<METHOD> <URL-PATH>`.  e.g.: `GET /tasks`.
</ResponseField>

<ResponseField name="sync_type" type="incremental | full" required>
  Specifies whether each sync execution replaces all of the data (`full`) or upserts it (`incremental`).

  Learn more about [incremental vs. full refresh](/implementation-guides/syncs/large-datasets) syncing.
</ResponseField>

<ResponseField name="runs" type="string">
  Specifies the frequency of the sync. Supports [ms](https://github.com/vercel/ms) notations.

  Defaults to 24h.
</ResponseField>

<ResponseField name="input" type="string">
  Defines the schema of the data required to run the sync. References a schema from the [models](#model-fields).

  Sync inputs are passed from your app to the sync function via the [connection metadata](/implementation-guides/building-integrations/customer-configuration).
</ResponseField>

<ResponseField name="scopes" type="string[]">
  Lists the necessary scopes to execute the sync.

  This list is just indicative; it doesn't trigger any automatic configuration (yet). List necessary scopes on the external API developer portal and your Nango UI integration settings.

  Defaults to no scope.
</ResponseField>

<ResponseField name="auto_start" type="boolean">
  If `true`, automatically starts synchronizing between the external API and Nango when a new connection is created. Otherwise, it needs to be triggered via the API or Nango UI.

  Defaults to `true`.
</ResponseField>

<ResponseField name="track_deletes" type="boolean">
  When `track_deletes` is set to `true`, Nango automatically detects deleted records during full syncs only and marks them as deleted in each record’s metadata (soft delete). These records remain stored in the cache.

  When set to `false`, Nango does not mark missing records as deleted, even if they weren’t returned in the latest full sync—they simply remain in the cache unchanged.

  Defaults to `false`.

  <Info>
    [Follow this guide](/implementation-guides/syncs/deletion-detection) to add support for deletion detection to your syncs.

    This setting only applies if `sync_type: full`. For incremental syncs, this setting is ignored; instead, you must flag deleted records in the sync function using `nango.batchDelete()` ([reference](/reference/functions)).
  </Info>
</ResponseField>

<ResponseField name="webhook-subscriptions" type="string | string[]">
  Lists the types of external webhooks the sync function will handle. Multiple syncs can listen to the same subscription. Learn more about [handling external webhooks in syncs](/implementation-guides/syncs/realtime-syncs).
</ResponseField>

### Action fields

Action configuration fields are under `integrations.<INTEGRATION-ID>.actions.<ACTION-NAME>`.

<ResponseField name="description" type="string" required>
  Describes the action.
</ResponseField>

<ResponseField name="output" type="string" required>
  Defines the schema of the data returned by the action. References a schema from the [models](#model-fields) section of this configuration file.

  Each action has a corresponding generated endpoint to trigger it, configured in the `endpoint` field below.
</ResponseField>

<ResponseField name="endpoint" type="string|object" required>
  Defines the endpoint to use to trigger the action.

  ```yaml
  endpoint:
    method: POST
    path: /tasks
  ```

  Possible method values are: `GET`, `POST`, `PUT`, `PATCH`, `DELETE`.

  The method/endpoint combination can be shared across actions to unify the communication with external APIs.
  The `group` is an optional value to group endpoints across functions.

  Legacy format: `<METHOD> <URL-PATH>`.  e.g.: `POST /tasks`.
</ResponseField>

<ResponseField name="input" type="string">
  Defines the schema of the data required to trigger the action. References a schema from the [Models](#model-fields).

  Action inputs are passed as parameters when triggering the action.
</ResponseField>

<ResponseField name="scopes" type="string[]">
  Lists the necessary scopes to trigger the action.

  This list is just indicative; it doesn't trigger any automatic configuration (yet). List necessary scopes on the external API developer portal and your Nango UI integration settings.

  Defaults to no scope.
</ResponseField>

### On-events fields

`on-events` configuration fields are under `integrations.<INTEGRATION-ID>.on-events.<EVENT-NAME>`.

<Tip>
  Nango currently supports the following events:

  - post-connection-creation
  - pre-connection-deletion

  Read the [Execute functions based on events](/implementation-guides/platform/implement-event-handler) guide.
</Tip>

<ResponseField name="post-connection-creation" type="string[]">
  Lists the functions to execute after a new connection is created.

  Example:

  ```yaml
  integrations:
    airtable:
      on-events:
        post-connection-creation:
          - setup # Name of your event-based function (without the .ts extension)
          - initialize-webhooks
  ```
</ResponseField>

<ResponseField name="pre-connection-deletion" type="string[]">
  Lists the functions to execute before a connection is deleted.

  Example:

  ```yaml
  integrations:
    airtable:
      on-events:
        pre-connection-deletion:
          - cleanup # Name of your event-based script (without the .ts extension)
          - remove-webhooks
  ```
</ResponseField>

### Basic types

For each model, you must define its fields and data types. Data types are based on Typescript types, with some tweaks:

| `nango.yaml` type                                     | Corresponding Typescript type |
| ----------------------------------------------------- | ----------------------------- |
| `bool` or `boolean`                                   | `boolean`                     |
| `string`                                              | `string`                      |
| `char` or `varchar`                                   | `string`                      |
| `integer` or `int` or `number` or `bigint` or `float` | `number`                      |
| `date`                                                | `Date`                        |
| `null`                                                | `null`                        |
| `undefined`                                           | `undefined`                   |
| `any`                                                 | `any`                         |
| `array`                                               | `any[]`                       |
| `object`                                              | `object`                      |
| `true` or `false`                                     | `true` or`false`              |

Types not listed here are not supported. If you think we are missing something, please reach out in the [Slack community](https://nango.dev/slack).

### Arrays

Your can use array types like this:

```yaml nango.yaml
models:
  Folder:
    files: string[]
    tickets: any[]
```

### Type & string unions

You can use union types such as:

```yaml nango.yaml
models:
  User:
    name: string | null | undefined
```

You can also use string unions to enforce specific values:

```yaml nango.yaml
models:
  User:
    gender: m | f
```

You can mix types and strings in unions:

```yaml nango.yaml
models:
  User:
    gender: male | female | null
```

<Info>
  When you use the `|` notation, we check each element against known Typescript types, to categorize it as type (if match) or string (if no match).
</Info>

### Union array

Your can create a union array:

```yaml nango.yaml
models:
  Folder:
    issues:
      - PullRequest
      - Issues
```

Which translates to the following generated Typescript model:

```ts
export interface Task {
  gender: (PullRequest | Issues)[];
}
```

### Reference other models

Your can use other models as types:

```yaml nango.yaml
models:
  User:
    id: string

  Account:
    users: User[]
```

### Extend types

You can have a model extend the properties of another base model:

```yaml nango.yaml
models:
  Issue:
    id: integer
    title: string
    author: string

  GithubIssue:
    __extends: Issue
    issue_number: string

  LinearIssue:
    __extends: Issue
    roadmap_id: string
```

### Dynamic field keys

You can allow dynamic keys in models:

```yaml nango.yaml
models:
  Task:
    __string: string
    id: string
```

Which translates to the following generated Typescript model:

```ts
export interface Task {
  [key: string]: string;
  id: string;
}
```

### Optional property

You can set a property as optional:

```yaml nango.yaml
models:
  Task:
    name?: string
```

### Unsupported syntax

A non-exhaustive list of unsupported syntax:

```yaml nango.yaml
models:
  Task:
    # Empty array
    name: []
    # Typescript utility types
    user: Pick<User>
```

# Deploying your configuration

Changes to your integration configuration become active once you deploy them to a Nango environment using the `nango deploy` CLI command.

These changes can have significant impacts, in particular, if you:

- Add a sync
- Remove a sync or an action
- Change a model or an integration script

### Adding a sync

Unless you sync configuration specifies `autoStart: false`, the deployment will kick off the data synchronization between the external API and Nango, for all relevant connections.

This change will be reflected in the Nango UI in _Integrations_ \> _select your integration_ \> _Endpoints_ tab.

### Removing a sync

Removing a sync will erase all the cached data related to that sync, for all relevant connections. The synced records will no longer be accessive via the Nango API & SDKs.

This change will be reflected in the Nango UI in _Integrations_ \> _select your integration_ \> _Endpoints_ tab.

<Warning>
  Changing the integration ID in your configuration is the equivalent of deleting the sync with the old integration ID, and creating a new one. So, the data cached by the old sync will be deleted (for all relevant connections).
</Warning>

### Removing an action

Removing an action will cause the failure of any request to trigger this action.

This change will be reflected in the Nango UI in _Integrations_ \> _select your integration_ \> _Endpoints_ tab.

### Changing a model or script

For full refresh syncs, as the data is replaced on each sync execution, the new model and script logic will apply to all records as soon as the sync executes following the deployment.

For incremental syncs, you can end up with model disparities, as older records will have outdated content. You will still be able to fetch them from the Nango cache. In some cases, it's better to trigger a full resync via the [API](/reference/api/sync/trigger) or the Nango UI, so that all historical records are fetched again using the new script & model.

<Warning>
  Changing a model name in your configuration is the equivalent of deleting the model with the old name, and creating a new one.
</Warning>

<Tip>
  **Questions, problems, feedback?** Please reach out in the [Slack community](https://nango.dev/slack).
</Tip>
